package com.jiangyg.mall.product.service;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.jiangyg.mall.core.exception.BusinessException;
import com.jiangyg.mall.db.mybatis.BaseServiceImpl;
import com.jiangyg.mall.core.support.restful.Pagination;
import com.jiangyg.mall.core.utils.bean.BeanUtils;
import com.jiangyg.mall.product.constant.ColumnConstant;
import com.jiangyg.mall.product.dto.BrandDTO;
import com.jiangyg.mall.product.dto.CategoryBrandDTO;
import com.jiangyg.mall.product.entity.Brand;
import com.jiangyg.mall.product.entity.Category;
import com.jiangyg.mall.product.entity.CategoryBrand;
import com.jiangyg.mall.product.vo.BrandVO;
import com.jiangyg.mall.product.vo.CategoryBrandVO;
import com.jiangyg.mall.product.dao.BrandDao;
import com.jiangyg.mall.product.dao.CategoryBrandDao;
import com.jiangyg.mall.product.dao.CategoryDao;
import org.apache.commons.lang.StringUtils;
import org.apache.dubbo.config.annotation.Service;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

@Service
public class BrandServiceImpl extends BaseServiceImpl<BrandDao, Brand> implements BrandService {

    /**
     * 分类
     */
    private final CategoryDao categoryDao;

    /**
     * 分类和品牌的关联关系
     */
    private final CategoryBrandDao categoryBrandDao;

    @Autowired
    public BrandServiceImpl(BrandDao brandDao,
                            CategoryDao categoryDao,
                            CategoryBrandDao categoryBrandDao) {
        super(brandDao);
        this.categoryDao = categoryDao;
        this.categoryBrandDao = categoryBrandDao;
    }

    @Override
    @Transactional(propagation = Propagation.NOT_SUPPORTED, readOnly = true)
    public Pagination<BrandVO> selectPagination(Pagination<BrandVO> pagination) throws Exception {
        return this.executeSelectPagination(pagination, BrandVO.class);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean saveOrUpdate(BrandDTO dto) throws Exception {
        Brand brand;
        final Long id = dto.getId();
        // 修改品牌信息
        if (id != null && (brand = this.baseMapper.selectById(id)) != null) {
            // 如果名称修改，则需要修改品牌分类关联表的品牌名称
            if (!StringUtils.equals(dto.getName(), brand.getName())) {
                final UpdateWrapper<CategoryBrand> wrapper = new UpdateWrapper<>();
                wrapper.eq(ColumnConstant.BRAND_ID, dto.getId());
                this.categoryBrandDao.update(new CategoryBrand(dto.getName()), wrapper);
            }
            BeanUtils.copyProperties(brand, dto);
            return this.baseMapper.updateById(brand) > 0;
        }
        // 新增品牌
        brand = new Brand();
        BeanUtils.copyProperties(brand, dto);
        return this.baseMapper.insert(brand) > 0;
    }

    @Override
    @Transactional(propagation = Propagation.NOT_SUPPORTED, readOnly = true)
    public BrandVO selectById(Long brandId) throws Exception {
        return this.executeSelectById(brandId, BrandVO.class);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean delete(List<Long> brandIds) {
        // 先删除品牌和分类的关联关系
        final UpdateWrapper<CategoryBrand> wrapper = new UpdateWrapper<>();
        wrapper.in(ColumnConstant.BRAND_ID, brandIds);
        this.categoryBrandDao.delete(wrapper);
        // 再删除品牌
        return this.baseMapper.deleteBatchIds(brandIds) > 0;
    }

    @Override
    @Transactional(propagation = Propagation.NOT_SUPPORTED, readOnly = true)
    public List<CategoryBrandVO> relationList(CategoryBrandDTO dto) throws Exception {
        final QueryWrapper<CategoryBrand> wrapper = new QueryWrapper<>();
        if (dto.getBrandId() != null) {
            wrapper.eq(ColumnConstant.BRAND_ID, dto.getBrandId());
        }
        if (dto.getCategoryId() != null) {
            wrapper.eq(ColumnConstant.CATEGORY_ID, dto.getCategoryId());
        }
        final List<CategoryBrand> dataList = categoryBrandDao.selectList(wrapper);
        return BeanUtils.transformList(dataList, CategoryBrandVO.class);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean relationSave(CategoryBrandDTO dto) throws Exception {
        // 品牌信息 和 分类信息
        final Brand brand = this.baseMapper.selectById(dto.getBrandId());
        final Category category = this.categoryDao.selectById(dto.getCategoryId());
        if (brand == null || category == null) {
            throw BusinessException.instance("mall.product.brand.cascader.save.notdata");
        }
        // 关系是否已存在
        final QueryWrapper<CategoryBrand> wrapper = new QueryWrapper<>();
        wrapper.eq(ColumnConstant.BRAND_ID, brand.getId());
        wrapper.eq(ColumnConstant.CATEGORY_ID, category.getId());
        final Integer count = this.categoryBrandDao.selectCount(wrapper);
        if (count > 0) {
            throw BusinessException.instance("mall.product.brand.cascader.save.hasReloation");
        }
        // 执行新增
        final CategoryBrand categoryBrand = new CategoryBrand();
        BeanUtils.copyProperties(categoryBrand, dto);
        categoryBrand.setBrandName(brand.getName());
        categoryBrand.setCategoryName(category.getName());
        return this.categoryBrandDao.insert(categoryBrand) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean relationDelete(CategoryBrandDTO dto) {
        final UpdateWrapper<CategoryBrand> wrapper = new UpdateWrapper<>();
        wrapper.eq(ColumnConstant.BRAND_ID, dto.getBrandId());
        wrapper.eq(ColumnConstant.CATEGORY_ID, dto.getCategoryId());
        return this.categoryBrandDao.delete(wrapper) > 0;
    }

}
